package game;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.EOFException;
import java.io.IOException;
import javax.microedition.lcdui.Graphics;
import javax.microedition.rms.RecordComparator;
import javax.microedition.rms.RecordEnumeration;
import javax.microedition.rms.RecordStore;
import javax.microedition.rms.RecordStoreException;
import javax.microedition.rms.RecordStoreNotOpenException;
/**
 * Record-Class
 * 
 * @author Group C03
 * @author Mona Khlousy
 * @author Heba El-Samahi 
 * @author Daniel Schobert
 *
 *
 */
public class LUMM2_records implements RecordComparator {
        
        private RecordStore recStore = null;
    
    /**
     * opens a recordstore and adds three scores to the recordstore
     */
    public LUMM2_records() {
        try {
            recStore = RecordStore.openRecordStore("scores", true);
            addScore(200, "Peter Pan");
            addScore(100, "Max Muster");
            addScore(300, "Andrea Anders");
        } catch (RecordStoreException rse) {
            System.out.println("rec store exception");
        }
    }

    /**
     * adds a score to the recordStore
     * @param score : the score which has been achieved by the player
     * @param playerName : the name of the player 
     */
    public void addScore(int score, String playerName) {
        int recId;  // returned by addRecord but not used
        if (!exists(playerName)){
        	ByteArrayOutputStream bos = new ByteArrayOutputStream();
        	DataOutputStream out = new DataOutputStream(bos);
        	try {
        		out.writeInt(score);
        		out.writeUTF(playerName);
        	} catch (IOException e) {
        		//TODO exception handling
        	}

        	byte[] b = bos.toByteArray();
        	try {
        		recId = recStore.addRecord(b, 0, b.length);
        	} catch (RecordStoreException rse) {
        		//TODO exception handling
        	}
        }
    }

    /**
     * checks if the name already exists in the recordStore (which means the player
     * is already listed in the HighScore)
     * 
     * @param name: playerName which has to be checked
     * @return true if name already exists in the highscore, 
     * false if no player with the given name is stored
     */
    public boolean exists(String name){
    	boolean exists = false;
    	RecordEnumeration re = null;
        try {
            re = recStore.enumerateRecords(null, this, true);
        } catch (RecordStoreNotOpenException e) {
            System.out.println("record store not open exception");
        }
    	try {
    		while (re.hasNextElement()) {
    			int id = re.nextRecordId();
    			ByteArrayInputStream bais = new ByteArrayInputStream(recStore.getRecord(id));
    			DataInputStream inputStream = new DataInputStream(bais);
    			try {
    				int score = inputStream.readInt();
            		String playerName = inputStream.readUTF();
            		if (playerName.equals(name)) {
            			exists = true;
            	    }
    			} catch (EOFException eofe) {
    				System.out.println("eof-exception");
    			}
    		}
    	} catch (Exception e) {
    		//TODO exception handling
    	}
    	return exists;
    }
  
    /**
     * prints the HighScores to the Screen
     * @param g Graphics
     */
    public void printScores(Graphics g) {
        g.setColor(0);
        g.fillRect(0, 0, LUMM2_Canvas.canvasWidth, LUMM2_Canvas.canvasHeight);
        g.setColor(255, 255, 255);
        printSortedScoresOnScreen(g);
    }
    
    /**
     * helper method to print scores on screen
     * @param g
     */
    private void printSortedScoresOnScreen(Graphics g) {
        int h = 75;
        g.drawString("H I G H   S C O R E s", 27, 25, 0);
        RecordEnumeration re = null;
        
        try {
                re = recStore.enumerateRecords(null, this, true);
        } catch (RecordStoreNotOpenException e) {
            System.out.println("record store not open exception");
        }
        
        try {
        		while (re.hasNextElement()) {
        			int id = re.nextRecordId();
        			ByteArrayInputStream bais = new ByteArrayInputStream(recStore.getRecord(id));
        			DataInputStream inputStream = new DataInputStream(bais);
        			try {
        				int score = inputStream.readInt();
                		String playerName = inputStream.readUTF();
                		g.drawString(score + "  " + playerName, 33, h, 0);
                		h += 25;
        			} catch (EOFException eofe) {
        				System.out.println("eof-exception");
        			}
        		}
        } catch (Exception e) {
        		//TODO exception handling
        }
        
    }
    
    /**
     * destroys the record-store
     */
    public void destroyRecords(){
        try {
            RecordEnumeration r = recStore.enumerateRecords(null, null, true);
            while(r.hasNextElement()){
                recStore.deleteRecord(r.nextRecordId());
            }
        } catch (Exception e){
        	System.out.println("exception in destroy records-method");
        }
    }
    
    /**
     * compares two scores, method inherited from interface RecordComparator
     * @param rec1 : score1 which has to be compared to
     * @param rec2 : score2 
     * @return 
     * 	RecordComparator.PRECEDES if rec1 > rec2
     *  RecordComparator.FOLLOWS if rec1 < rec2
     *  RecordComparator.EQUIVALENT if rec1 == rec2
     * 	
     */
    public int compare(byte[] rec1, byte[] rec2) {
            ByteArrayInputStream bais1 = new ByteArrayInputStream(rec1);
            DataInputStream inputStream1 = new DataInputStream(bais1);
            ByteArrayInputStream bais2 = new ByteArrayInputStream(rec2);
            DataInputStream inputStream2 = new DataInputStream(bais2);
            int score1 = 0;
            int score2 = 0;
            try {
                // Extract the scores.
                score1 = inputStream1.readInt();
                score2 = inputStream2.readInt();
            } catch (EOFException eofe) {
                System.out.println(eofe);
                eofe.printStackTrace();
            } catch (IOException eofe) {
                System.out.println(eofe);
                eofe.printStackTrace();
            }

            // Sort by score
            if (score1 > score2) {
                return RecordComparator.PRECEDES;
            } else if (score1 < score2) {
                return RecordComparator.FOLLOWS;
            } else {
                return RecordComparator.EQUIVALENT;
            }
     }
}